package com.imessage.action.api.client;

import com.bean.*;
import com.imessage.action.api.BaseAction;
import com.imessage.jackson.JsonObject;
import com.imessage.type.BaseConfigCode;
import com.imessage.type.BusinessTaskCmd;
import com.imessage.type.BusinessTaskState;
import com.imessage.type.DeviceClientState;
import com.imessage.utils.DateUtil;
import com.imessage.vo.MenuVo;
import com.imessage.vo.api.ApiClientVo;
import io.ebean.Expr;
import io.ebean.Expression;
import lombok.extern.slf4j.Slf4j;
import org.apache.commons.lang3.StringUtils;

import java.util.ArrayList;
import java.util.Date;
import java.util.List;


@Slf4j
public class ApiClientBaseAction extends BaseAction {


    protected void setExpressionList(List<Expression> expressionList, MenuVo menuVo) {
        if (StringUtils.isNotBlank(menuVo.getName())) {
            expressionList.add(Expr.contains("name", menuVo.getName()));
        }
        if (StringUtils.isNotBlank(menuVo.getUrl())) {
            expressionList.add(Expr.contains("url", menuVo.getUrl()));
        }
    }

    protected DeviceClient getDeviceClient(ApiClientVo apiClientVo){
        DeviceClient deviceClient=baseService.findObject(
                DeviceClient.class, Expr.eq("code", apiClientVo.getClientCode()));
        if(deviceClient==null){
            deviceClient=new DeviceClient();
            deviceClient.setCode(apiClientVo.getClientCode());
            deviceClient.setName(apiClientVo.getClientCode());
            deviceClient.setVirtualNum(apiClientVo.getVirtualNum());
            deviceClient.setTaskCmd(BusinessTaskCmd.other);
            deviceClient.setState(DeviceClientState.run);
            baseService.saveObject(deviceClient);
        }else{
            deviceClient.setVirtualNum(apiClientVo.getVirtualNum());
            deviceClient.setState(DeviceClientState.run);
            baseService.updateObject(deviceClient);
        }
       return  deviceClient;
    }


    protected DeviceVirtual getRightDeviceVirtual(DeviceClient deviceClient, long virtualNum){
        List<String> codeList=new ArrayList<String>();
        codeList.add(BaseConfigCode.virtual_max_exist_num.getCode());
        codeList.add(BaseConfigCode.virtual_max_run_num.getCode());
        List<BaseConfig> baseConfigList=configService.findList(codeList);
        long virtualMaxExistNum=500;
        long virtualMaxRunNum=5;
        for(BaseConfig baseConfig:baseConfigList){
            if(StringUtils.isBlank(baseConfig.getValue())){
               continue;
            }
            if(baseConfig.equals(BaseConfigCode.virtual_max_exist_num)){
                try{
                    virtualMaxExistNum=Long.valueOf(baseConfig.getValue());
                }catch (Exception e){
                    log.error("", e);
                }
            }
            if(baseConfig.equals(BaseConfigCode.virtual_max_run_num)){
                try{
                    virtualMaxRunNum=Long.valueOf(baseConfig.getValue());
                }catch (Exception e){
                    log.error("", e);
                }
            }
        }
        if(virtualNum>=virtualMaxExistNum){//大于最大数量
            return virtualService.findFinishVirtual(deviceClient);//找到需要删除的虚拟机
        }
        //获取正在运行的虚拟机数量
        long virtualCurrRunNum=virtualService.getRunVirtualCount(deviceClient);
        if(virtualCurrRunNum>=virtualMaxRunNum){
            //返回新的虚拟机
            return virtualService.getNewDeviceVirtual(deviceClient);
        }
        //获取需要启动的虚拟机
        DeviceVirtual deviceVirtual=virtualService.findNeedRunVirtual(deviceClient);
        if(deviceVirtual!=null){
            return deviceVirtual;
        }
        //获取需要删除的虚拟机
        deviceVirtual=virtualService.findNeedFinishVirtual(deviceClient);
        if(deviceVirtual!=null){
            return deviceVirtual;
        }
        //返回新的虚拟机
        return virtualService.getNewDeviceVirtual(deviceClient);
    }





    protected BusinessTaskDetail getRunBusinessTaskDetail(DeviceVirtual deviceVirtual){
        if(deviceVirtual==null){
            return null;
        }
        if(!deviceVirtual.getTaskState().equals(BusinessTaskState.finish)){
            return null;
        }
        BusinessTaskCmd nextBusinessTaskCmd=null;
        if(deviceVirtual.getTaskCmd().equals(BusinessTaskCmd.other)){
            nextBusinessTaskCmd=BusinessTaskCmd.copy_modify_virtual;
        }
        if(deviceVirtual.getTaskCmd().equals(BusinessTaskCmd.copy_modify_virtual)){
            nextBusinessTaskCmd=BusinessTaskCmd.start_virtual;
        }
        if(deviceVirtual.getTaskCmd().equals(BusinessTaskCmd.send_single_msg)){
            long maxSilenceTime=50*60*60;
            BaseConfig baseConfig=configService.findObject(BaseConfigCode.max_silence_time);
            if(StringUtils.isNotBlank(baseConfig.getValue())){
                try{
                    maxSilenceTime=Long.valueOf(baseConfig.getValue());
                }catch (Exception e){
                    log.error("", e);
                }
            }
            double currSilenceTime=DateUtil.minuSecond(
                    deviceVirtual.getUpdatedTime(), new Date());
            if(currSilenceTime>=maxSilenceTime){
                nextBusinessTaskCmd=BusinessTaskCmd.send_batch_msg;
            }else{
                return null;
            }
        }
        if(deviceVirtual.getTaskCmd().equals(BusinessTaskCmd.send_batch_msg)){
            nextBusinessTaskCmd=BusinessTaskCmd.del_virtual;
        }
        BusinessTaskDetail businessTaskDetail=null;
        if(nextBusinessTaskCmd.equals(BusinessTaskCmd.send_batch_msg)){
            businessTaskDetail=
                    taskService.getNewBusinessTaskDetail(BusinessTaskCmd.start_virtual,deviceVirtual);
            if(businessTaskDetail!=null){
                deviceVirtual.setTaskCmd(BusinessTaskCmd.send_single_msg);
                deviceVirtual.setTaskState(BusinessTaskState.finish);
                baseService.updateObject(deviceVirtual);
            }
        }else{
            businessTaskDetail=
                    taskService.getNewBusinessTaskDetail(nextBusinessTaskCmd,deviceVirtual);
            if(businessTaskDetail!=null){
                deviceVirtual.setTaskCmd(businessTaskDetail.getCmd());
                deviceVirtual.setTaskState(businessTaskDetail.getState());
                baseService.updateObject(deviceVirtual);
            }
        }
        return businessTaskDetail;
    }


    protected void initGetObject(
            JsonObject dataObject, DeviceVirtual deviceVirtual,
            BusinessTaskDetail businessTaskDetail){
        dataObject.put("task_id", businessTaskDetail.getId()+"");
        if(businessTaskDetail.getCmd().equals(BusinessTaskCmd.shutdown_virtual)){
            dataObject.put("task_cmd", BusinessTaskCmd.shutdown_virtual.getCode());
        }else{
            dataObject.put("task_cmd", businessTaskDetail.getCmd().getCode());
        }
        dataObject.put("virtual_name", deviceVirtual.getVirtualName());
        dataObject.put("virtual_mac", deviceVirtual.getVirtualMac());
    }


}
